package com.house.framework.service.impl;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.house.framework.service.ExportService;
import com.house.framework.vo.ExportExcel;
import com.house.utils.PathKit;
import lombok.SneakyThrows;
import org.apache.poi.hssf.usermodel.*;
import org.apache.poi.ss.usermodel.*;
import org.springframework.stereotype.Service;

import java.io.File;
import java.io.FileOutputStream;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@Service
public class ExportServiceImpl implements ExportService {

    @SneakyThrows
    @Override
    public JSONObject exportExcel(JSONObject form) {
        final String exportPath = PathKit.getClassPath();
        ExportExcel exportExcel = getExportExcel(form);
        HSSFWorkbook workbook = new HSSFWorkbook();
        HSSFSheet sheet = workbook.createSheet(exportExcel.getExcelName());
        HSSFRow rowTitle = sheet.createRow(0);
        rowTitle.setHeightInPoints(30);

        HSSFFont font2 = workbook.createFont();
        font2.setBoldweight (HSSFFont.BOLDWEIGHT_BOLD);

        HSSFCellStyle cellStyle = workbook.createCellStyle();
//        cellStyle.setAlignment(HSSFCellStyle.ALIGN_CENTER); // 居中
        cellStyle.setFillForegroundColor(IndexedColors.PALE_BLUE.getIndex());
        cellStyle.setFillPattern(CellStyle.SOLID_FOREGROUND);
        cellStyle.setVerticalAlignment(VerticalAlignment.CENTER);
        cellStyle.setBorderBottom(BorderStyle.THIN);
        cellStyle.setBorderLeft(BorderStyle.THIN);
        cellStyle.setBorderRight(BorderStyle.THIN);
        cellStyle.setBorderTop(BorderStyle.THIN);
        cellStyle.setFont(font2);

        HSSFCellStyle cellStyleRow = workbook.createCellStyle();
        cellStyleRow.setVerticalAlignment(VerticalAlignment.CENTER);
        cellStyleRow.setBorderBottom(BorderStyle.THIN);
        cellStyleRow.setBorderLeft(BorderStyle.THIN);
        cellStyleRow.setBorderRight(BorderStyle.THIN);
        cellStyleRow.setBorderTop(BorderStyle.THIN);

//        cellStyle.setAlignment(HorizontalAlignment.CENTER);

        String[] rowName = exportExcel.getRowName();
        int columnNum = rowName.length;

        //绘制表头
        for (int i = 0; i < rowName.length; i++) {
            HSSFCell cell = rowTitle.createCell(i, CellType.STRING);
            cell.setCellValue(rowName[i].substring(rowName[i].indexOf(':') + 2, rowName[i].length() - 2));
            cell.setCellStyle(cellStyle);
        }

        //调整数据
        List<Map<String, Object>> dataList = exportExcel.getDataList();

        List<Object[]> list = new ArrayList<>();
        for (Map<String, Object> map : dataList) {
            List<String> data = new ArrayList<>();
            for (String s : rowName) {
                String str = s.substring(2, s.indexOf(":") - 1);
                int flag = 0;
                for (Map.Entry<String, Object> entry : map.entrySet()) {
                    String key = entry.getKey();
                    if (str.equals(key)) {
                        data.add(String.valueOf(entry.getValue()));
                        flag = 1;
                        break;
                    }
                }
                if (flag == 0){
                    data.add("--");
                }
            }
            Object[] objects = data.toArray();
            list.add(objects);
        }

        //添加数据
        for (int i = 0; i < list.size(); i++) {
            Object[] objects = list.get(i);
            HSSFRow row = sheet.createRow(i+1);
            for (int j = 0; j < objects.length; j++) {
                HSSFCell  cell = null;   //设置单元格的数据类型
                cell = row.createCell(j,HSSFCell.CELL_TYPE_STRING);
                if(!"".equals(objects[j]) && objects[j] != null){
                    cell.setCellValue(objects[j].toString());  //设置单元格的值
                    cell.setCellStyle(cellStyleRow);
                    row.setHeightInPoints(20);
                }
            }
        }

        setExcelStyle(sheet, columnNum);

        OutputStream output = null;
        File file = new File(exportPath + "/Excel");
        if (!file.exists()) {
            file.mkdirs();
        }
        output = new FileOutputStream(new File(file, exportExcel.getExcelName() + ".xls"));
        workbook.write(output);
        output.close();
        JSONObject object = new JSONObject();
        object.put("name", exportExcel.getExcelName());
        return object;
    }

    /**
     * 获取excel表的对象
     *
     * @param jsonObject 前端参数
     * @return 对象
     */
    private ExportExcel getExportExcel(JSONObject jsonObject) {
        ExportExcel exportExcel = new ExportExcel();

        List<Map<String, Object>> dataList = new ArrayList<>();
        List<String> list = new ArrayList<>();
        String[] rowName = null;
        JSONArray title = jsonObject.getJSONArray("title");
        for (int i = 0; i < title.size(); i++) {
            list.add(title.getString(i));
        }

        rowName = list.toArray(new String[list.size()]);

        JSONArray content = jsonObject.getJSONArray("content");
        for (int i = 0; i < content.size(); i++) {
            HashMap<String, Object> hashMap = new HashMap<>(content.getJSONObject(i));
            dataList.add(hashMap);
        }

        String excelName = jsonObject.getString("excelName");
        exportExcel.setExcelName(excelName);
        exportExcel.setRowName(rowName);
        exportExcel.setDataList(dataList);

        return exportExcel;
    }

    /**
     * 让列宽随着导出的列长自动适应
     *
     * @param sheet     Excel
     * @param columnNum 列数
     */
    private void setExcelStyle(HSSFSheet sheet, int columnNum) {
        //让列宽随着导出的列长自动适应
        for (int colNum = 0; colNum < columnNum; colNum++) {
            int columnWidth = sheet.getColumnWidth(colNum) / 256;
            for (int rowNum = 0; rowNum < sheet.getLastRowNum(); rowNum++) {
                HSSFRow currentRow;
                //当前行未被使用过
                if (sheet.getRow(rowNum) == null) {
                    currentRow = sheet.createRow(rowNum);
                } else {
                    currentRow = sheet.getRow(rowNum);
                }
                if (currentRow.getCell(colNum) != null) {
                    HSSFCell currentCell = currentRow.getCell(colNum);
                    if (currentCell.getCellType() == HSSFCell.CELL_TYPE_STRING) {
                        int length = currentCell.getStringCellValue().getBytes().length;
                        if (columnWidth < length) {
                            columnWidth = length;
                        }
                    }
                }
            }
            sheet.setColumnWidth(colNum, (columnWidth + 4) * 256);
        }
    }
}
